package com.mew.common.dc.redis;

import cn.hutool.core.date.DateUtil;
import com.mew.common.config.RedisConstantValue;
import com.mew.common.util.DateUtils;
import com.mew.common.vo.task.TaskBO;
import com.mew.common.vo.task.UserTaskBO;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

/**
 * 任务 redis
 * @author dylin
 * @create 2021/3/29
 */
@Service
@Slf4j
public class TaskRedisService {
    @Autowired
    private RedisTemplate<String, Object> redisTemplate;

    /**
     * 查询大厅任务库
     * @return
     */
    public List<TaskBO> findLobbyTaskLibrary(){
        List<Object> list = redisTemplate.opsForHash().values(RedisConstantValue.TASK_LOBBY_LIBRARY);
        if (null == list || list.isEmpty()){
            return null;
        }
        return list.stream().map(o -> (TaskBO)o).collect(Collectors.toList());
    }

    /**
     * 查询游戏任务库
     * @param gameId 游戏ID
     * @return
     */
    public List<TaskBO> findGameTaskLibrary(Integer gameId){
        List<Object> list = redisTemplate.opsForHash().values(String.format(RedisConstantValue.TASK_GAME_LIBRARY,gameId));
        if (null == list || list.isEmpty()){
            return null;
        }
        return list.stream().map(o -> (TaskBO)o).collect(Collectors.toList());
    }
    /**
     * 查询玩家大厅任务
     * @param userId 玩家ID
     * @return
     */
    public List<UserTaskBO> findUserLobbyTaskList(Long userId){
        List<Object> list = redisTemplate.opsForHash().values(String.format(RedisConstantValue.TASK_LOBBY_USER, userId));
        if (null == list || list.isEmpty()){
            return null;
        }
        return list.stream().map(o -> (UserTaskBO)o).collect(Collectors.toList());
    }

    /**
     * 查询用户指定大厅任务
     * @param userId 玩家ID
     * @param taskId 任务ID
     * @return
     */
    public UserTaskBO findUserLobbyTaskByID(Long userId,Integer taskId){
        Object task = redisTemplate.opsForHash().get(String.format(RedisConstantValue.TASK_LOBBY_USER, userId), taskId);
        return (UserTaskBO) task;
    }
    /**
     * 查询玩家游戏任务
     * @param gameId 游戏ID
     * @param userId 玩家ID
     * @return
     */
    public List<UserTaskBO> findUserGameTaskList(Integer gameId,Long userId){
        List<Object> list = redisTemplate.opsForHash().values(String.format(RedisConstantValue.TASK_GAME_USER,gameId,userId));
        if (null == list || list.isEmpty()){
            return null;
        }
        return list.stream().map(o -> (UserTaskBO)o).collect(Collectors.toList());
    }

    /**
     * 查询用户指定游戏任务
     * @param gameId 游戏ID
     * @param userId 玩家ID
     * @param taskId 任务ID
     * @return
     */
    public UserTaskBO findUserGameTaskByID(Integer gameId,Long userId,Integer taskId){
        Object task = redisTemplate.opsForHash().get(String.format(RedisConstantValue.TASK_GAME_USER,gameId,userId), taskId);
        return (UserTaskBO) task;
    }

    /**
     * 插入玩家大厅任务
     * @param userId 玩家ID
     * @param taskBOList 任务列表
     */
    public void putUserLobbyTask(long userId,List<TaskBO> taskBOList){
        String key=String.format(RedisConstantValue.TASK_LOBBY_USER,userId);
        taskBOList.stream().forEach(taskBO -> {
            UserTaskBO userTaskBO=UserTaskBO.builder().taskBO(taskBO).currentVal(0L).isFinish(0).isReceiveAward(0).build();
            redisTemplate.opsForHash().put(key,taskBO.getId(),userTaskBO);
        });
        setTaskExpire(key);
    }

    /**
     * 插入玩家游戏任务
     * @param gameId 游戏ID
     * @param userId 玩家ID
     * @param taskBOList 任务列表
     */
    public void putUserGameTask(int gameId,long userId,List<TaskBO> taskBOList){
        String key=String.format(RedisConstantValue.TASK_GAME_USER,gameId,userId);
        taskBOList.stream().forEach(taskBO -> {
            UserTaskBO userTaskBO=UserTaskBO.builder().taskBO(taskBO).currentVal(0L).isFinish(0).isReceiveAward(0).build();
            redisTemplate.opsForHash().put(key,taskBO.getId(),userTaskBO);
        });
        setTaskExpire(key);
    }

    /**
     * 更新玩家大厅任务
     * @param userId 玩家ID
     * @param userTaskBO 任务
     */
    public void updateUserLobbyTask(Long userId,UserTaskBO userTaskBO){
        if(findUserLobbyTaskByID(userId,userTaskBO.getTaskBO().getId())==null){
            return;
        };
        redisTemplate.opsForHash().put(String.format(RedisConstantValue.TASK_LOBBY_USER,userId),userTaskBO.getTaskBO().getId(),userTaskBO);
    }

    /**
     * 更新玩家游戏任务
     * @param gameId 游戏ID
     * @param userId 玩家ID
     * @param userTaskBO 任务
     */
    public void updateUserGameTask(Integer gameId,Long userId,UserTaskBO userTaskBO){
        if(findUserGameTaskByID(gameId,userId,userTaskBO.getTaskBO().getId())==null){
            return;
        };
        redisTemplate.opsForHash().put(String.format(RedisConstantValue.TASK_GAME_USER,gameId,userId),userTaskBO.getTaskBO().getId(),userTaskBO);
    }

    /**
     * 计算过期时间
     * @param key
     */
    private void setTaskExpire(String key){
        //设置过期时间为第二天六点
        long ex= DateUtil.betweenMs(DateUtil.date(), DateUtils.getOffsetTimeDate(6,1));
        redisTemplate.expire(key,ex,TimeUnit.MILLISECONDS);
    }
}
